package com.uchedao.vehicledetection.activity.blue_tooth;

import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;

import com.uchedao.mybaselibrary.utils.LogUtil;
import com.uchedao.vehicledetection.utils.ConversionUtil;

import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.util.UUID;

/**
 * 蓝牙工具2.0
 * Created by zhengxizhen on 15/9/29.
 */
public class BluetoothUtils {

    private String TAG = "BluetoothUtils";

    private BluetoothAdapter adapter;
    private BluetoothDevice remoteDevice;
    private String address;
    private int mRetryCount;
    private BluetoothSocket bluetoothSocket;
    private IBluetooth2Listener listener;
    private ConnectedThread mConnectedThread;
    private boolean isStarting;// 开始

    private static BluetoothUtils instance = new BluetoothUtils();

    public static BluetoothUtils getInstance() {
        return instance;
    }

    /**
     * 开启
     */
    public void startDF_5000(String _address) {
        if (isStarting) {
            return;
        }
        isStarting = true;
        address = _address;
        adapter = BluetoothAdapter.getDefaultAdapter();
        if (!adapter.isEnabled()) {
            //直接打开蓝牙
            adapter.enable();
        }
        BluetoothDevice device = adapter.getRemoteDevice(address);
        if (device.getBondState() != BluetoothDevice.BOND_BONDED) {// 判断给定地址下的device是否已经配对
            try {
                ClsUtils.autoBond(device.getClass(), device, "0000");// 设置pin值
                ClsUtils.createBond(device.getClass(), device);
                remoteDevice = device;
                LogUtil.e(TAG, "配对成功");
                sendPairingSuccess();
            } catch (Exception e) {
                e.printStackTrace();
                LogUtil.e(TAG, "配对不成功");
                sendPairingFail();
                return;
            }
        } else {
            LogUtil.e(TAG, "配对成功");
            remoteDevice = device;
            sendPairingSuccess();
        }
        // 客户端建立一个BluetoothSocket类去连接远程蓝牙设备
        try {
            startThread();
        } catch (Exception e) {
            LogUtil.e(TAG, "df" + e.getMessage());
            e.printStackTrace();
            sendReadFail();
        }

    }

    private void startThread() throws Exception {
        if (mConnectedThread != null) {
            mConnectedThread.closeThread();
            mConnectedThread = null;
        }
        mConnectedThread = new ConnectedThread();
        mConnectedThread.isContinue = true;
        mConnectedThread.start();
    }

    /**
     * 建立一个BluetoothSocket类去连接远程蓝牙设备
     */
    public class ConnectedThread extends Thread {

        private DataInputStream mmInStream;
        private DataOutputStream mmOutStream;
        //Continue
        private boolean isContinue = true;

        private void init() {
            isContinue = true;
            mRetryCount++;
            try {
                if (!adapter.isEnabled()) {
                    adapter.enable();
                }
                UUID uuid = UUID.fromString("00001101-0000-1000-8000-00805F9B34FB");
                bluetoothSocket = remoteDevice.createInsecureRfcommSocketToServiceRecord(uuid);
                // bluetoothSocket =
                // ClsUtils.createBluetoothSocket(remoteDevice);
                if (!bluetoothSocket.isConnected()) {
                    bluetoothSocket.connect();// 尝试连接
                    LogUtil.e(TAG, "=====蓝牙连接成功====");
                    sendConnectSuccess();
                }
            } catch (Exception e) {
                e.printStackTrace();
                if (mRetryCount % 2 == 0) {// 没重试两次报一次错误
                    LogUtil.e(TAG, "蓝牙连接错误");
                    isContinue = false;
                    sendConnectFail();
                } else {
                    try {
                        Thread.sleep(3000);
                    } catch (Exception e1) {
                        e1.printStackTrace();
                    }
                    init();
                    return;
                }
            }
            LogUtil.e(TAG, "create ConnectedThread");
            DataInputStream tmpIn = null;
            DataOutputStream tmpOut = null;
            try {
                tmpIn = new DataInputStream(bluetoothSocket.getInputStream());
                tmpOut = new DataOutputStream(bluetoothSocket.getOutputStream());
            } catch (Exception e) {
                e.printStackTrace();
                LogUtil.e(TAG, "temp sockets not created:" + e.getMessage());
                isContinue = false;
                sendConnectFail();
            }

            mmInStream = tmpIn;
            mmOutStream = tmpOut;
        }

        /**
         * 关闭线程
         */
        public synchronized void closeThread() {
            try {
                notify();
                cancel();
                interrupt();
            } catch (Exception e) {
                e.printStackTrace();
            }
        }

        @Override
        public void run() {
            init();
            parseDataDF();
            super.run();
        }

        /**
         * 解析漆膜仪数据
         */
        private void parseDataDF() {
            int _read_length;
            int start = 0;
            int length = 0;
            while (isContinue) {
                LogUtil.e(TAG, "df_data==================等待接收");
                sendReadData();
                try {
                    byte[] start_buffer = new byte[1];
                    _read_length = mmInStream.read(start_buffer);
                    LogUtil.e(TAG, "df_data==================读取开始位:" + _read_length);
                    if (_read_length != 1) {
                        continue;
                    }
                    start = Integer.parseInt(ConversionUtil.bytesToHexString(start_buffer), 16);
                    if (start != 170) {// AA 开始位
                        continue;
                    }
                    LogUtil.e(TAG, "df_data==================开始位:" + start);
                    byte[] length_buffer = new byte[1];
                    _read_length = mmInStream.read(length_buffer);
                    LogUtil.e(TAG, "df_data==================读取长度位:" + _read_length);
                    if (_read_length != 1) {
                        continue;
                    }
                    length = Integer.parseInt(ConversionUtil.bytesToHexString(length_buffer), 16);
                    LogUtil.e(TAG, "df_data==================长度位:" + length);
                    if (length > 3) {
                        byte[] readBuf = new byte[length];
                        readBuf[0] = start_buffer[0];
                        readBuf[1] = length_buffer[0];
                        int position = 2;
                        while (position < length) {
                            LogUtil.e(TAG, "df_data==================position:" + position);
                            readBuf[position] = mmInStream.readByte();//按位读取数据
                            position++;
                        }
                        if (position == length && listener != null) {//读取成功
                            LogUtil.e(TAG, "df_data==================读取成功:" + ConversionUtil.bytesToHexString(readBuf));
                            //返回数据
                            listener.sendReceiveData(readBuf);
                        }
                    }

                } catch (Exception e) {
                    e.printStackTrace();
                    LogUtil.e(TAG, "蓝牙断开:" + e.getMessage());
                    isContinue = false;
                    sendConnectFail();
                }
            }

        }

        public void cancel() {
            isContinue = false;
            try {
                if (null != bluetoothSocket) {
                    bluetoothSocket.close();
                    bluetoothSocket = null;
                }
                if (null != mmInStream) {
                    mmInStream.close();
                    mmInStream = null;
                }
                if (null != mmOutStream) {
                    mmOutStream.close();
                    mmOutStream = null;
                }
            } catch (IOException e) {
                e.printStackTrace();
                LogUtil.e(TAG, "close() of connect socket failed:" + e.getMessage());
            }
        }
    }

    public void setListener(IBluetooth2Listener _listener) {
        this.listener = _listener;
    }

    private void sendConnectFail() {
        if (listener != null) {
            listener.sendConnectFail();
        }
    }

    private void sendPairingFail() {
        if (listener != null) {
            listener.sendPairingFail();
        }
    }

    private void sendReadData() {
        if (listener != null) {
            listener.sendReadData();
        }
    }

    private void sendConnectSuccess() {
        if (listener != null) {
            listener.sendConnectSuccess();
        }
    }


    private void sendPairingSuccess() {
        if (listener != null) {
            listener.sendPairingSuccess();
        }
    }

    private void sendReadFail() {
        if (listener != null) {
            listener.sendReadFail();
        }
    }


    public void close() {
        isStarting = false;
        if (mConnectedThread != null) {
            mConnectedThread.cancel();
            mConnectedThread = null;
        }

        try {
            if (remoteDevice != null) {
                ClsUtils.removeBond(remoteDevice.getClass(), remoteDevice);
            }
            if (adapter != null && adapter.isEnabled()) {
                adapter.cancelDiscovery();
                adapter.disable();
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
